﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;

namespace Cocon90.Lib.Util
{
    /// <summary>
    /// 线程池， 允许指定数量的线程在池中运行。
    /// </summary>
    public class ThreadPoolEx
    {
        private System.Collections.Queue threadQueue;
        public System.Collections.Queue ThreadQueue { get { return threadQueue; } set { threadQueue = value; } }
        /// <summary>
        /// 最大线程数量
        /// </summary>
        public int MaxThreadCount { get; set; }
        /// <summary>
        /// 构建线程池 需传入最大线程数量。如果线程数量满了，它会停止最先执行的线程，并替换其为最新线程。
        /// </summary>
        /// <param name="maxThreadCount"></param>
        public ThreadPoolEx(int maxThreadCount)
        {
            this.MaxThreadCount = maxThreadCount;
            threadQueue = new System.Collections.Queue();
        }
        /// <summary>
        /// 取得一个可用线程。如果线程数量满了，它会停止最先执行的线程，并替换其为最新线程。
        /// </summary>
        /// <returns></returns>
        public Thread CreateThread(ThreadStart threadStart)
        {
            if (threadQueue.Count < MaxThreadCount)
            { //如果池中线程还可再创建。
                Thread thread = new Thread(threadStart);
                thread.Name = "thread" + Guid.NewGuid().ToString("N");
                threadQueue.Enqueue(thread);//加入末尾
                return thread;
            }
            else
            {//如果池中线程已经满了。
                var oldThread = (Thread)threadQueue.Dequeue();
                try
                {
                    oldThread.Abort();
                }
                catch { }
                Thread thread = new Thread(threadStart);
                thread.Name = "thread" + Guid.NewGuid().ToString("N");
                threadQueue.Enqueue(thread);//加入末尾
                return thread;
            }
        }
        /// <summary>
        /// 取得一个可用线程。如果线程数量满了，它会停止最先执行的线程，并替换其为最新线程。
        /// </summary>
        /// <returns></returns>
        public Thread CreateThread(ParameterizedThreadStart threadStart)
        {
            if (threadQueue.Count < MaxThreadCount)
            { //如果池中线程还可再创建。
                Thread thread = new Thread(threadStart);
                thread.Name = "thread" + Guid.NewGuid().ToString("N");
                threadQueue.Enqueue(thread);//加入末尾
                return thread;
            }
            else
            {//如果池中线程已经满了。
                var oldThread = (Thread)threadQueue.Dequeue();
                try
                {
                    oldThread.Abort();
                }
                catch { }
                Thread thread = new Thread(threadStart);
                thread.Name = "thread" + Guid.NewGuid().ToString("N");
                threadQueue.Enqueue(thread);//加入末尾
                return thread;
            }
        }
    }
}
